#region Using References

using System;
using System.Collections.Generic;
using System.Diagnostics.Contracts;

#endregion

namespace Beaker.Services.FileSystem
{
	[ContractClass( typeof( FolderContracts ) )]
	public interface IFolder
		: IFileSystemEntry
	{
		/// <summary>
		/// Gets the files in this folder.
		/// </summary>
		/// <returns>
		/// A sequence of files.
		/// </returns>
		IEnumerable<IFile> GetFiles();

		/// <summary>
		/// Gets the file with the given name.
		/// </summary>
		/// <param name="fileName">The name of the file to get.</param>
		/// <returns>The file with the given name, or <c>null</c> when it could not be found.</returns>
		IFile GetFile( string fileName );

		/// <summary>
		/// Gets the folders in this folder.
		/// </summary>
		/// <returns>
		/// A sequence of folders.
		/// </returns>
		IEnumerable<IFolder> GetFolders();

		/// <summary>
		/// Gets the folder with the given name.
		/// </summary>
		/// <param name="folderName">The name of the folder to get.</param>
		/// <returns>The folder with the given name, or <c>null</c> when it could not be found.</returns>
		IFolder GetFolder( string folderName );

		/// <summary>
		/// Gets the entires in this folder.
		/// </summary>
		/// <returns>
		/// A sequence of items.
		/// </returns>
		IEnumerable<IFileSystemEntry> GetEntries();

		/// <summary>
		/// Gets the entry with the given name in this folder.
		/// </summary>
		/// <param name="entryName">Name of the entry to get.</param>
		/// <returns>The entry with the given name, or <c>null</c> when it could not be found.</returns>
		IFileSystemEntry GetEntry( string entryName );
	}

	[ContractClassFor( typeof( IFolder ) )]
	public abstract class FolderContracts
		: IFolder
	{
		#region Implementation of IFolder

		/// <summary>
		/// Gets the files in this folder.
		/// </summary>
		/// <returns>
		/// A sequence of files.
		/// </returns>
		public IEnumerable<IFile> GetFiles()
		{
			Contract.Ensures( Contract.Result<IEnumerable<IFile>>() != null );
			throw new NotImplementedException();
		}

		/// <summary>
		/// Gets the file with the given name.
		/// </summary>
		/// <param name="fileName">The name of the file to get.</param>
		/// <returns>The file with the given name, or <c>null</c> when it could not be found.</returns>
		public IFile GetFile( string fileName )
		{
			// result can be null
			throw new NotImplementedException();
		}

		/// <summary>
		/// Gets the folders in this folder.
		/// </summary>
		/// <returns>
		/// A sequence of folders.
		/// </returns>
		public IEnumerable<IFolder> GetFolders()
		{
			Contract.Ensures( Contract.Result<IEnumerable<IFolder>>() != null );
			throw new NotImplementedException();
		}

		/// <summary>
		/// Gets the folder with the given name.
		/// </summary>
		/// <param name="folderName">The name of the folder to get.</param>
		/// <returns>The folder with the given name, or <c>null</c> when it could not be found.</returns>
		public IFolder GetFolder( string folderName )
		{
			// result can be null
			throw new NotImplementedException();
		}

		/// <summary>
		/// Gets the entires in this folder.
		/// </summary>
		/// <returns>
		/// A sequence of items.
		/// </returns>
		public IEnumerable<IFileSystemEntry> GetEntries()
		{
			Contract.Ensures( Contract.Result<IEnumerable<IFileSystemEntry>>() != null );
			throw new NotImplementedException();
		}

		/// <summary>
		/// Gets the entry with the given name in this folder.
		/// </summary>
		/// <param name="entryName">Name of the entry to get.</param>
		/// <returns>The entry with the given name, or <c>null</c> when it could not be found.</returns>
		public IFileSystemEntry GetEntry( string entryName )
		{
			// result can be null
			throw new NotImplementedException();
		}

		#endregion

		#region Implementation of IFileSystemEntry

		/// <summary>
		/// Gets the name of the entry
		/// </summary>
		string IFileSystemEntry.Name
		{
			get { throw new NotImplementedException(); }
		}

		/// <summary>
		/// Get the folder this entry is in
		/// </summary>
		IFolder IFileSystemEntry.ParentFolder
		{
			get { throw new NotImplementedException(); }
		}

		#endregion
	}
}